package de.uni_saarland.coli.doclists.data.btree.nodes;

import java.io.Serializable;

import de.uni_saarland.coli.doclists.data.btree.INode;
import de.uni_saarland.coli.doclists.index.filesystem.DiscList;

/**
 * @author stefan Inteface of B-Tree nodes.
 * 
 *         This class implements the shared functionality of bucket and non
 *         bucket nodes. Mostly the key managment.
 * 
 * @param <T>
 *            The type of data.
 */
public abstract class BaseNode<T> implements INode<T>, Serializable {
	/**
	 * 
	 */
	private static final long serialVersionUID = -8671370894601811961L;

	/**
	 * the child ids
	 */
	protected int[] childIds;

	/**
	 * the nodes id
	 */
	protected int nodeID;

	protected DiscList parentList;
	
	/**
	 * initializes the node.
	 */
	protected void initialize() {
		this.nodeID = 0;
		this.childIds = new int[3];
		for (int i = 0; i < 3; i++) {
			this.childIds[i] = Integer.MAX_VALUE;
		}
		this.parentList = null;
	}

	@Override
	public int getNodeID() {
		return this.nodeID;
	}

	@Override
	public void setListIDX(int idx) {
		this.nodeID = idx;
	}

	@Override
	public int getListIDX() {
		return this.nodeID;
	}
	
	@Override
	public void setDistList(DiscList list) {
		this.parentList = list;
	}

	@Override
	public boolean isFull() {
		return this.childIds[2] != Integer.MAX_VALUE;
	}

	/**
	 * Returns the child ids.
	 * 
	 * @return the child ids
	 */
	public int[] getChildIDs() {
		return this.childIds;
	}

	/**
	 * Shifts the key to the left starting at the index
	 * 
	 * @param idx
	 *            the index
	 */
	public void shiftKeysLeft(int idx) {
		for (int i = 2; i > idx; i--) {
			this.childIds[i] = this.childIds[i - 1];
		}
	}

	/**
	 * Return the index of a link
	 * 
	 * @param key
	 *            the key
	 */
	public int findLink(int key) {
		int idx = 0;
		while (idx < 3 && key > this.childIds[idx])
			idx++;

		return idx;
	}
	
	protected void updateDistListEntry() {
		if (this.parentList != null)
			this.parentList.updateData(this.nodeID, this.toBytes());
	}
}
